using System;
using System.Data;
using System.Diagnostics;
using System.Text;
using AllInOnePluginBL.Helpers;
using AllInOnePluginBL.Rules;
using AllInOnePluginBL.SiteScrappers;

namespace AllInOnePluginBL.jobs
{
    /// <summary>
    /// Summary description for MaintenanceJob
    /// </summary>
    public class MaintenanceJob : BaseScrapperJob
    {
        #region Private const
        private const int RUN_TIME_INTERVAL_IN_HOURS = 24;
        #endregion

        #region Ctor
        public MaintenanceJob()
            : base(RUN_TIME_INTERVAL_IN_HOURS, JobType.Maintainance)
        {
        }
        #endregion

        #region Implementation of IJob
        public override void Execute()
        {
            try
            {
                _log.Info(string.Format("Start Executing MaintenanceJob at {0}", DateTime.Now.ToString("r")));

                //leteMegaVideoLinks();

                //UpdateTopDownVideos();
                //CheckTVShowsLinks();
                //CheckVideoLinks();
                //UpdateHebSubFlag();
                //MergeSeriesNames();
                //MergeMoviesLinks();

                _log.Info(string.Format("End Executing MaintenanceJob at {0}", DateTime.Now.ToString("r")));
            }
            catch (Exception ex)
            {
                _log.ErrorException("Error Executing MaintenanceJob", ex);
            }
            finally
            {
                UpdateMainJobRunTime();
            }
        }
        #endregion

        #region Private Methods
        
        private void DeleteMegaVideoLinks()
        {
            DeleteVideos();
            DeleteTVShows();
        }

        private void DeleteVideos()
        {
            try
            {
                var videos = _pluginDBHandler.GetAllVideos();
                foreach (var video in videos)
                {
                    video.VideosLinks.Load();
                    if (video.VideosLinks.Count == 0)
                        _pluginDBHandler.DeleteVideo(video);
                }
            }
            catch (Exception ex)
            {
               
            }
        }

        private void DeleteTVShows()
        {
            try
            {
                var tvShows = _pluginDBHandler.GetAllTVShows();
                foreach (var tvShow in tvShows)
                {
                    tvShow.TVShowsLinks.Load();
                    if (tvShow.TVShowsLinks.Count == 0)
                        _pluginDBHandler.DeleteTVShow(tvShow);
                }
            }
            catch (Exception ex)
            {
            }
        }

        private void UpdateJobRunTime(string jobName)
        {
            try
            {
                var job = _pluginDBHandler.GetJob(jobName) ??
                          _pluginDBHandler.CreateJob(jobName, _jobType.ToString());

                var pluginDBHandler = PluginDBHandler.Instance;
                pluginDBHandler.UpdateJobRunTime(job.JobID, DateTime.Now);
            }
            catch (Exception ex)
            {
                _log.ErrorException(string.Format("Error UpdateJobRunTime: {0}", jobName), ex);
            }
        }

        private void UpdateTopDownVideos()
        {
            var videos = _pluginDBHandler.GetMoviesBySite(26);
            foreach (var video in videos)
            {
                try
                {
                    var pageContent = Utils.GetPage(video.PluginUrl, Encoding.GetEncoding("windows-1255"));
                    string plot, imageUrl;
                    TopDownMeParserJob.GetPlotAndImage(pageContent, out plot, out imageUrl);

                    if (string.IsNullOrEmpty(video.Plot))
                    {
                        video.Plot = plot;
                        video.ImageUrl = imageUrl;
                        _pluginDBHandler.SaveAllVideos();
                    }
                }
                catch (Exception ex)
                {
                    _log.ErrorException("MaintenanceJob::UpdateTopDownVideos", ex);
                }
            }

            UpdateJobRunTime("UpdateTopDownVideos");
        }

        private void CheckVideoLinks()
        {
            try
            {
                var videoLinks = _pluginDBHandler.GetAllVideosLinks(true);
                foreach (var videoLink in videoLinks)
                {
                    string errorText;
                    videoLink.IsValid = !Utils.IsBrokenLink(videoLink.LinkURL, out errorText);

                    if (videoLink.IsValid.Value)
                        videoLink.ValidDate = DateTime.Now;

                    videoLink.ErrorText = errorText;

                    Debug.WriteLine(string.Format("videoLink:{0} - {1}", videoLink.LinkID, videoLink.IsValid));
                    _pluginDBHandler.SaveAllVideos();
                }
                UpdateJobRunTime("CheckVideoLinks");
            }
            catch (Exception ex)
            {
                Console.WriteLine("Error in CheckVideoLinks {0}", ex.Message);
            }
        }

        private void CheckTVShowsLinks()
        {
            try
            {

                var tvShowsLinks = _pluginDBHandler.GetAllTVShowsLinks();
                foreach (var tvShowsLink in tvShowsLinks)
                {
                    string errorText;
                    tvShowsLink.IsValid = !Utils.IsBrokenLink(tvShowsLink.LinkURL, out errorText);

                    if (tvShowsLink.IsValid.Value)
                        tvShowsLink.ValidDate = DateTime.Now;

                    tvShowsLink.ErrorText = errorText;
                    _pluginDBHandler.SaveAllTVShows();

                    Debug.WriteLine(string.Format("tvShowsLink:{0} - {1}", tvShowsLink.LinkID, tvShowsLink.IsValid));
                }


            }
            catch (Exception ex)
            {
                Console.WriteLine("Error in CheckTVShowsLinks {0}", ex.Message);
            }
        }

        private void UpdateHebSubFlag()
        {
            try
            {
                var videos = _pluginDBHandler.GetAllVideos();
                foreach (var video in videos)
                {
                    var subRule = new IsHebSubMovieRule();
                    video.Is_Heb_Sub = subRule.IsHebSub(video.HebrewVideoName) ? 1 : 0;

                    var dubRule = new IsHebDubMovieRule();
                    video.Is_Heb_Dub = dubRule.IsHebDub(video.HebrewVideoName) ? 1 : 0;

                    if (video.EntityState == EntityState.Modified)
                        _pluginDBHandler.SaveAllVideos();

                    Debug.WriteLine(string.Format("video:{0} - Is_Heb_Sub:{1} - Is_Heb_Dub:{2}", video.HebrewVideoName, video.Is_Heb_Sub, video.Is_Heb_Dub));
                }
            }
            catch (Exception ex)
            {
                Console.WriteLine("Error in UpdateHebSubFlag {0}", ex.Message);
            }
        }

        private void MergeSeriesNames()
        {
            try
            {
                _pluginDBHandler.MergeSeriesNames();
            }
            catch (Exception ex)
            {
                Console.WriteLine("Error in MergeSeriesNames {0}", ex.Message);
            }
        }

        private void MergeMoviesLinks()
        {
            try
            {
                _pluginDBHandler.MergeMoviesLinks();
            }
            catch (Exception ex)
            {
                Console.WriteLine("Error in MergeMoviesLinks {0}", ex.Message);
            }
        }
        #endregion
    }
}